w,h = 1200,800
add_library('sound')
shape_side = 80
rows = h/shape_side
cols = w/shape_side
hitted = {}
colors = {}
color_list = [
              color(254, 67, 101),color(252, 157, 154),color(249, 205, 173),color(200, 200, 169),color(131, 175, 155),
              ]
numbs = {}
state = {
         'state':'moving1',
         'click':False,
         'clicked_position':None,
         'moving_position':None,
         'clicked_position2':None
         }
anime_list = {}
for j in range(rows):
    for i in range(cols):
        p = shape_side*i,shape_side*j
        n = int(random(1,5))
        colors[p] = color_list[n-1]
        numbs[p] = n
        
bg_color = 255
icon_imgs = []
def setup():
    size(w,h)
    background(bg_color)
    
    icon1 = loadImage('pintu1.png')
    icon2 = loadImage('pintu2.jpg')
    icon3 = loadImage('pintu3.png')
    icon4 = loadImage('pintu4.jpg')
    icon5 = loadImage('pintu6.png')
    icon6 = loadImage('pintu8.png')
    global icon_imgs
    global obj_voice
    obj_voice = SoundFile(this, 'obj.wav')
    global bgm
    bgm = SoundFile(this, 'bgm.mp3')
    icon_imgs = [icon1,icon2,icon3,icon4,icon5,icon6]

def top_left_collide(rect_x,rect_y,x,y):
    if   rect_x<x<rect_x + shape_side:
        if rect_y < y < rect_y+ shape_side:
            return True
    return False



def draw_():
    background(bg_color)
    clicks = []
    for j in range(rows):
        for i in range(cols):
          
            p = shape_side*i,shape_side*j
            if hitted.get(p):
                continue
            fill(colors[p] )
            if top_left_collide(shape_side*i,shape_side*j,mouseX,mouseY):
                if state['state'] == 'moving1':
                    state['moving_position'] = p
                elif state['state'] == 'pressed1':
                    state['clicked_position'] = p
                    print(state)
                #stroke(250,0,0)
       
            stroke(0)
            #rect(shape_side*i,shape_side*j,shape_side,shape_side)
            image(icon_imgs[numbs[(shape_side*i,shape_side*j)]%6],shape_side*i,shape_side*j,shape_side,shape_side)
    if  state['moving_position'] :
        if not hitted.get(  state['moving_position'] ):
            x,y =  state['moving_position'] 
            stroke(200,0,0)
            fill(colors[(x,y)] )
            rect(x,y,shape_side,shape_side)
    if state['clicked_position'] :
        if not hitted.get(  state['clicked_position'] ):
            stroke(0,0,250)
            x,y =  state['clicked_position'] 
            fill(colors[(x,y)] )
            rect(x,y,shape_side,shape_side)
    for j in range(rows):
        for i in range(cols):
          
            p = shape_side*i,shape_side*j
            if hitted.get(p):
                continue
            x,y = p
            fill(255)
            text(numbs[p],x+20,y+20)
            
    for k,d in anime_list.items():
        m = float(millis())/1000
        s = d['start']
        if m <  d['start']+d['duration']:
            for i in range(len(d['lines'])):
                if i == 0 :continue
                stroke(0,0,255)
                x1,y1 = d['lines'][i-1]
                x2,y2 = d['lines'][i]
                line(x1+20,y1+20, x2+20,y2+20)
                
def draw():
    hits = [k for k,v in hitted.items() if v ]
    if len(hits) == cols * rows:
        background(255)
        textSize(20)
        fill(0)
        text('Win',w/2,h/2)
    else:
        draw_()
        

def get_all_p():
    res = []
    for j in range(rows):
        for i in range(cols):
          
            p = shape_side*i,shape_side*j
            res.append(p)
    return res

def has_line_path(rects):
    print(rects)
    return rects == [] or all([hitted.get(p,False) for p in rects])


    
    
def get_inner_rects(pa,pb):
    xa,ya = pa
    xb,yb = pb
    
    rects = get_all_p()
    if xa == xb:
        i = 0
        rects_ = [p for p in rects if p[i] ==pa[i] and min(pa[1-i],pb[1-i]) <p[1-i]<max(pa[1-i],pb[1-i]) ]
        return rects_
    elif ya == yb:
        i = 1
        rects_ = [p for p in rects if p[i] ==pa[i] and min(pa[1-i],pb[1-i]) <p[1-i]<max(pa[1-i],pb[1-i]) ]
        return rects_
    return None
def has_two_line_path(pa,pb):
    xa,ya = pa
    xb,yb = pb
    print('--s--')
    rects = get_all_p()
    rects_= get_inner_rects(pa,pb)
    if xa != xb and ya!=yb:
        return False
    if has_line_path(rects_):
        return True
 
    print('--end--')
    return False

def has_corner_path(pa,pb):
    xa,ya = pa
    xb,yb = pb
    pc = xa,yb
    pd = xb,ya
    if has_two_line_path(pa,pc) and has_two_line_path(pc,pb):
        return True
    if has_two_line_path(pa,pd) and has_two_line_path(pd,pb):
        return True
    return False
def has_path(pa,pb):
    if colors[pa]!= colors[pb]:
        print('not color')
        return False
    if has_two_line_path(pa,pb):
        rects_= get_inner_rects(pa,pb)
        anime_list['line'] = {'lines':[pa]+rects_+[pb],'start':float(millis())/1000 , 'duration':2.0}
        print('has two')
        return True
    print('Xhas two')
    if has_corner_path(pa,pb):
        return True
    return False
    
def mousePressed():
    global obj_voice
    for j in range(rows):
        for i in range(cols):
            p = shape_side*i,shape_side*j
            fill(colors[p] )
            
            if top_left_collide(shape_side*i,shape_side*j,mouseX,mouseY):
                if  state['state'] == 'moving1':
                    state['clicked_position'] = p
                    state['state'] ='moving2'
                elif  state['state'] == 'moving2':
                    if p!=state['clicked_position']:
                        state['clicked_position2'] = p
                        state['state'] = 'click2'
    if state['state'] == 'click2':
        if has_path( state['clicked_position'], state['clicked_position2']):
            print('has path')
            hitted[ state['clicked_position']] = True
            hitted[ state['clicked_position2']] = True
            obj_voice.play()
        state['state'] ='moving1'
        state['clicked_position']  = None
        state['clicked_position2']  = None
        
def keyPressed():
    if key == 'q':
        state['state'] = 'moving'
    if key == 'p':
        print(state)

            
